package com.starview.platform.data.value;

import com.starview.platform.data.EvaluationException;
import com.starview.platform.data.IConstructor;
import com.starview.platform.data.IValue;
import com.starview.platform.data.IValueVisitor;
import com.starview.platform.data.type.IType;
import com.starview.platform.data.type.TypeUtils;
import com.starview.star.compiler.util.PrettyPrintDisplay;
import com.starview.star.compiler.util.PrettyPrintable;
import com.starview.star.operators.string.runtime.ValueDisplay;

@SuppressWarnings("serial")
public class TupleRow implements PrettyPrintable, Comparable<TupleRow>, IConstructor
{
  final int entryNo;
  final IConstructor entry;
  public final static String tupleRowLabel = "__tupleRow";

  TupleRow(int entryNo, IConstructor entry)
  {
    this.entry = entry;
    this.entryNo = entryNo;
  }

  @Override
  public void prettyPrint(PrettyPrintDisplay disp)
  {
    disp.append(entryNo);
    disp.append(":");
    ValueDisplay.display(disp, entry);
  }

  @Override
  public String toString()
  {
    return PrettyPrintDisplay.toString(this);
  }

  @Override
  public boolean equals(Object obj)
  {
    return obj instanceof TupleRow && ((TupleRow) obj).entryNo == entryNo;
  }

  @Override
  public int hashCode()
  {
    return entryNo;
  }

  @Override
  public int compareTo(TupleRow other)
  {
    return entryNo - other.entryNo;
  }

  @Override
  public IType getType()
  {
    return TypeUtils.typeExp(tupleRowLabel, entry.getType());
  }

  @Override
  public void accept(IValueVisitor visitor)
  {
    visitor.visitConstructor(this);
  }

  @Override
  public int conIx()
  {
    return 0;
  }

  @Override
  public String getLabel()
  {
    return tupleRowLabel;
  }

  @Override
  public int size()
  {
    return 1;
  }

  @Override
  public IValue getCell(int index)
  {
    if (index == 0)
      return entry;
    else
      throw new IllegalArgumentException("index out of range");
  }

  @Override
  public void setCell(int index, IValue value) throws EvaluationException
  {
    throw new EvaluationException("not permitted");
  }

  @Override
  public IValue[] getCells()
  {
    throw new UnsupportedOperationException("not permitted");
  }

  @Override
  public IConstructor copy() throws EvaluationException
  {
    return shallowCopy();
  }

  @Override
  public IConstructor shallowCopy() throws EvaluationException
  {
    return this;
  }
}